package gov.pbc.nn.kjgl.software.dao;

import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;

import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Restrictions;
import org.springframework.stereotype.Repository;

import com.bstek.bdf2.core.context.ContextHolder;
import com.bstek.dorado.core.Configure;
import com.bstek.dorado.data.entity.EntityState;
import com.bstek.dorado.data.entity.EntityUtils;
import com.bstek.dorado.data.provider.Criteria;
import com.bstek.dorado.data.provider.Page;

import gov.pbc.nn.core.dao.AbstractHibernateDao;
import gov.pbc.nn.kjgl.entity.Project;
import gov.pbc.nn.kjgl.entity.ProjectFile;
import gov.pbc.nn.kjgl.entity.ProjectMember;
import gov.pbc.nn.kjgl.entity.ProjectProblem;

@Repository
public class ProjectProblemDao extends AbstractHibernateDao {

	/**
	 * 问题表数据
	 * 
	 * @param page
	 * @param projectId
	 */
	public void getProjectProblem(Page<ProjectProblem> page,Criteria criteria, String Id) {
		DetachedCriteria query = this.buildDetachedCriteria(criteria, ProjectProblem.class);
		query.add(Restrictions.or(Restrictions.eq("invalid", false), Restrictions.isNull("invalid")));
		query.add(Restrictions.eq("projectId", Id));
		this.pagingQuery(page,query);
	}

//	/**
//	 * 当前登陆人所参与的项目
//	 * 
//	 * @return
//	 */
//	public List<Project> getProject() {
//		String hql = "select distinct projectId from ProjectMember where invalid=false and username=:username";
//		Map<String, Object> map = new HashMap<String, Object>();
//		map.put("username", ContextHolder.getLoginUserName());
//		List<String> ls = this.query(hql, map);
//		List<Project> list = new ArrayList<Project>();
//		if (ls != null) {
//			String hql1 = "from Project where invalid=false and id=:projectId and state=10";
//			Map<String, Object> map1 = new HashMap<String, Object>();
//			for (int i = 0; i < ls.size(); i++) {
//				map1.put("projectId", ls.get(i));
//				List<Project> lss = this.query(hql1, map1);
//				if (!lss.isEmpty()) {
//					list.add(lss.get(0));
//				}
//			}
//		}
//		return list;
//	}

	public void loadProject(Page<Project> page,Criteria criteria, String Id) {
		DetachedCriteria query = DetachedCriteria.forClass(Project.class);
		query.add(Restrictions.or(Restrictions.eq("invalid", false), Restrictions.isNull("invalid")));
		query.add(Restrictions.eq("projectId", Id));
		query.add(Restrictions.eq("state", 10));
		this.pagingQuery(page, query);
	}
	
	/**
	 * 下拉框 选择人员
	 * 
	 * @param projectId
	 * @return
	 */
	public List<ProjectMember> getProjectMember(String projectId) {
		DetachedCriteria query = DetachedCriteria.forClass(ProjectMember.class);
		query.add(Restrictions.or(Restrictions.eq("invalid", false), Restrictions.isNull("invalid")));
		query.add(Restrictions.eq("projectId", projectId));
		return (List<ProjectMember>) this.query(query);
	}
	
	/**
	 * 查询 问题管理文件（问题管理文件 type=3）
	 * @return
	 */
	public void getProjectFile(Page<ProjectFile> page,String id) {
		DetachedCriteria query = DetachedCriteria.forClass(ProjectFile.class);
		query.add(Restrictions.or(Restrictions.eq("invalid", false), Restrictions.isNull("invalid")));
		query.add(Restrictions.eq("type", 3));
		query.add(Restrictions.eq("ownerId", id));
		this.pagingQuery(page, query);
	}

	/**
	 * 保存添加问题
	 * @param projectProblem
	 * @throws IOException 
	 */
	public void saveProjectProblem(ProjectProblem projectProblem,String Id) throws IOException {
		EntityState state = EntityUtils.getState(projectProblem);
			if (state.equals(EntityState.NEW)) {//新增的时候执行
				//保存问题表数据
				projectProblem.setBeginTime(new Date());
				projectProblem.setProposer(ContextHolder.getLoginUserName());
				projectProblem.setProposerName(ContextHolder.getLoginUser().getCname());
				projectProblem.setProjectId(Id);
				this.save(projectProblem);
				//得到 上传文件内容
				List<ProjectFile> files=  EntityUtils.getValue(projectProblem,"dataSetFile"); 
				if(files!=null){
					//声明一个map集合，将临时路径存进去，否则在保存实际路径的时候会将临时路径覆盖
					Map<String,String> tmpMap = new HashMap<String,String>();
					for(int i=0;i<files.size();i++){
						ProjectFile pf = files.get(i);
						pf.setOwnerId(projectProblem.getId());
						pf.setType(3);
						tmpMap.put("File"+i, pf.getPath());//map存放临时路径,没有保存到数据库中。（缓存）
						pf.setPath(this.getRealPath().toString());//将实际路径保存到数据库中
						this.save(pf);
					}
					for(int i=0;i<files.size();i++){
						ProjectFile pf = files.get(i);
						String key = "File"+i;
						String tmpPath = tmpMap.get(key);//根据key 得到临时路径
						this.transterFile(tmpPath,pf.getPath());//临时文件更新为实际路径
					}
				}
			} else if (state.equals(EntityState.MODIFIED)) {
				this.update(projectProblem);
			}
	}
	
	/**
	 * 得到实际文件路径
	 * 
	 * @return 
	 * @throws IOException
	 */
	public Path getRealPath() throws IOException{
		String basePath = Configure.getString("WENJIAN_FILE_UPLOAD_PATH");
		String pathArr = "问题附件";
		Path path = Paths.get(basePath, pathArr);//组合2个路径
		if (!Files.isDirectory(path)) {
			path = Files.createDirectories(path);
		}
		path = path.resolve(UUID.randomUUID().toString());
		return path;//上传文件保存后的实际地址
	}
	
	/** 
	 *  将 临时文件路径 更新 实际文件路径
 	 * @param sourceFile 实际文件路径
	 * @param targetFile 临时文件路径
	 * @throws IOException
	 */
	private void transterFile(String sourceFile,String targetFile) throws IOException{
		Path sourcePath = Paths.get(sourceFile);
		Files.copy(sourcePath, Paths.get(targetFile));
	}

}
